#ifndef _PHOENIX_H
#define _PHOENIX_H

#include <iostream>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <pthread.h>
#include <math.h>
#include <typeinfo>
#include<semaphore.h>

#include <opencv4/opencv2/opencv.hpp>
#include <opencv4/opencv2/highgui.hpp>
#include <opencv2/opencv.hpp>

#include "ArmorDector.h"
#include "general.h"
#include "opencv_extend.h"
#include "serial.h"
#include "log.h"
#include "img_buffer.h"
#include "camera.h"
#include"serial.h"
#include"Buff.h"
#include"state.h"



// Phoenix接口，方便之后添加兵种
class Phoenix
{
public:

    Phoenix();

    ~Phoenix();

    //海康相机读取图片函数，不需要更改-------生产者
    void Produce();

    //纯虚函数从下位机读取数据，需要在子类中重写（不同兵种不同通信）
    virtual void Sense() = 0;

    //对获取到的图片进行一系列处理，同样是纯虚函数，需要重写 -------消费者
	virtual void Consume() = 0;
    
    thread ProduceThread();

    thread ConsumeThread();

    thread SenseThread();

private:
    /* 相机 */
    Mycamera mycamera;

    /* Angle solver */
    //PNPSolver p4pSolver;

    //神符识别
    BuffDetector detect;

protected:
    /*图片缓存*/
    ImgBuffer _buffer;

    /* 串口 */
    Serial serial;

    //设计模式（状态模式）  ， 车不同状态转换
    shared_ptr<Work> _workState;
    volatile  int _task;
    volatile int _shootTask;

    //信号量，线程同步（可以用互斥量，这里因为我刚刚学了信号量，用了信号量的话图片缓冲区就没用了）
    sem_t sem_pro;
    sem_t sem_com;

    //互斥量
    std::mutex _mutex;

    //debug用来计时的类，查看帧率
    CELLTimestamp _tTime;

};


//兵种工厂（抽象工厂） 用来实例化我们的兵种对象
class RMFactory
{
public:
    RMFactory(){}
    ~RMFactory(){}
    virtual shared_ptr<Phoenix> creatPhoenix() = 0;
}; 

#endif


